package com.hzeport.bgs22emduty.util;

import com.hzeport.bgs22emduty.entity.BaseGroupUserRelation;
import com.hzeport.bgs22emduty.entity.BasePersonInfo;
import com.hzeport.bgs22emduty.entity.ParamGroupDuty;
import com.hzeport.bgs22emduty.entity.ParamScheduleSetting;
import com.hzeport.bgs22emduty.enums.DTypeEnum;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;

import java.util.Comparator;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
import java.util.stream.IntStream;

@Component
@RequiredArgsConstructor
@Slf4j
public class DutySortUtil {

    final private GuavacacheUtils guavacacheUtils;

    /**
     * 将排班人员按照群组排序，群组顺序为 dutyGroups顺序
     *
     * @param persons    排班人员
     * @param dutyGroups 排班群组
     * @return 排序后排班人员列表
     *
     */
    public List<BasePersonInfo> sortPerson(List<BasePersonInfo> persons, List<ParamGroupDuty> dutyGroups) {
        List<BaseGroupUserRelation> allUserRelations = guavacacheUtils.getUserGroupRelation();
        // key: userId; value: groupId;
        // todo: 同一个人有两个群组，如何处理？
        final Map<String, String> map = allUserRelations.stream().collect(Collectors.toMap(
                BaseGroupUserRelation::getUserId, BaseGroupUserRelation::getGroupId,
                (a, b) -> a));
        persons.forEach(item -> item.setGroupId(map.get(item.getUserno())));
        // 生成群组顺序的映射  key: groupId; value: 序号
        final Map<String, Integer> orderMap = IntStream.range(0, dutyGroups.size())
                .boxed().collect(Collectors.toMap(
                        idx -> dutyGroups.get(idx).getGroupId(), idx -> idx,
                        (a, b) -> a));

        return persons.stream().sorted(Comparator
                .comparingInt((BasePersonInfo i) -> orderMap.getOrDefault(i.getGroupId(), Integer.MAX_VALUE)) // 依群组顺序排序
                .thenComparing(PersonCompareUtil.comparePersonForSort())    // 根据globalSort 排序
        ).collect(Collectors.toList());
    }

    /**
     * 排序排班配置 上午 -> 下午 -> 夜间， 白天 -> 夜间，
     *
     * @param scheduleSettings 原始排班配置列表
     * @return 排序后排版配置列表
     */
    public List<ParamScheduleSetting> sortParamScheduleSetting(List<ParamScheduleSetting> scheduleSettings) {
        return scheduleSettings.stream()
                .sorted(Comparator.comparingInt(o -> DTypeEnum.getSortByCode(o.getParamDutyType())))
                .collect(Collectors.toList());
    }

}
